home *** CD-ROM | disk | FTP | other *** search
/ BBS in a Box 5 / BBS in a Box -Volume V (BBS in a Box) (April 1992).iso / Files / Apple / Apple II TNs(Text).cpt / Apple II TNs(Text) / PDOS / TN.PDOS.021 / TN.PDOS.021
Encoding:
Text File  |  1989-11-15  |  20.9 KB  |  405 lines  |  [TEXT/pdos]

  1. Apple II
  2. Technical Notes
  3. _____________________________________________________________________________
  4.                                                   Developer Technical Support
  5.  
  6.  
  7. ProDOS 8
  8. #21:    Identifying ProDOS Devices
  9.  
  10. Revised by:    Dave Lyons & Matt Deatherage                         July 1989
  11. Written by:    Matt Deatherage & Dan Strnad                     November 1988
  12.  
  13. This Technical Note describes how to identify ProDOS devices and their 
  14. characteristics given the ProDOS unit number.  This scheme should only be used 
  15. under ProDOS 8.
  16. Changes since November 1988:  Added a section on things to avoid.
  17. _____________________________________________________________________________
  18.  
  19. There are various reasons why an application would want to identify ProDOS 
  20. devices.  Although ProDOS itself takes great pains to treat all devices 
  21. equally, it has internal drivers for two types of devices:  Disk II drives and 
  22. the /RAM drive provided on 128K or greater machines.  Because all devices 
  23. really are not equal (i.e., some cannot format while others are read-only, 
  24. etc.), a developer may need to know how to identify a ProDOS device.
  25.  
  26. Although the question of how much identification is subjective for each 
  27. developer, ProDOS 8 offers a fair level of identification; the only devices 
  28. which cannot be conclusively identified are those devices with RAM-based 
  29. drivers, and they could be anything.  The vast majority of ProDOS devices can 
  30. be identified, however, so you could prompt the user to insert a disk in 
  31. UniDisk 3.5 #2, instead of Slot 2, Drive 2, which could be confusing if the 
  32. user has a IIc or IIGS.
  33.  
  34. Note that for the majority of applications, this level of identification is 
  35. unnecessary.  Most applications simply prompt the user to insert a disk by its 
  36. name, and the user can place it in any drive which is capable of working with 
  37. the media of the disk.  You should avoid requiring a certain disk to be in a 
  38. specific drive since doing so defeats much of the device-independence which 
  39. gives ProDOS 8 its strength.
  40.  
  41. When you do need to identify a device (i.e., if you need to format media in a 
  42. Disk II or /RAM device), however, the process is fairly straightforward.  This 
  43. process consists of a series of tests, any one of which could end with a 
  44. conclusive device identification.  It is not possible to look at a single ID 
  45. byte to determine a particular device type.  You may determine rather quickly 
  46. that a device is a SmartPort device, or you may go all the way through the 
  47. procedure to identify a third-party network device.  For those developers who 
  48. absolutely must identify devices, we present the following discussion.
  49.  
  50.  
  51. Isn't There Some Kind of "ID Nibble?"
  52.  
  53. ProDOS 8 does not support an "ID nibble."  Section 5.2.4 of the ProDOS 8 
  54. Technical Reference Manual states that the low nibble of each unit number in 
  55. the device list "is a device identification:  0 = Disk II, 4 = Profile, $F = 
  56. /RAM."
  57.  
  58. When ProDOS 8 finds a "smart" ProDOS block device while doing its search of 
  59. the slots and ports, it copies the high nibble of $CnFE (where n is the slot 
  60. number) into the low nibble of the unit number in the global page.  The low 
  61. nibble then has the following definition:
  62.  
  63.     Bit 3:      Medium is removable
  64.     Bit 2:      Device is interruptible
  65.     Bit 1-0:    Number of volumes on the device (minus one)
  66.  
  67. As you can see, it is quite easy for the second definition to produce one of 
  68. the original values (e.g., 0, 4, or $F) in the same nibble for completely 
  69. different reasons.  You should ignore the low nibble in the unit number in the 
  70. global page when identifying devices since the first definition is 
  71. insufficient to uniquely identify devices and the second definition contains 
  72. no information to specifically identify devices.  Once you do identify a 
  73. ProDOS block device, however, you may look at $CnFE to obtain the information 
  74. in the second definition above, as well as information on reading, writing, 
  75. formatting, and status availability.
  76.  
  77. When identifying ProDOS devices, we start with a list of unit numbers for all 
  78. currently installed disk devices.  As we progress through the identification 
  79. process, we will identify some devices while we will not know about others 
  80. until the end of the process.
  81.  
  82.  
  83. Starting with the Unit Number
  84.  
  85. ProDOS unit numbers (unit_number) are bytes where the bits are arranged in the 
  86. pattern DSSS0000, where D = 0 for drive one and D = 1 for drive two, SSS is a 
  87. three-bit integer with values from one through seven indicating the device 
  88. slot number (zero is not a valid slot number), and the low nibble is ignored.
  89.  
  90. To obtain a list of the unit numbers for all currently installed ProDOS disk 
  91. devices, you can perform a ProDOS MLI ON_LINE call with a unit number of $00.  
  92. This call returns a unit number and a volume name for every device in the 
  93. device list.  ProDOS stores the length of the volume name in the low nibble of 
  94. the unit number which ON_LINE returns; if an error occurs, the low nibble will 
  95. contain $0 and the byte immediately following the unit number will contain an 
  96. error code.  For more information on the ON_LINE call, see section 4.4.6 of 
  97. the ProDOS 8 Technical Reference Manual.  We will discuss the error codes in 
  98. more detail later in this Note.
  99.  
  100. To identify the devices in the device list, we need to know in which physical 
  101. slot the hardware resides, so we can look at the slot I/O ROM space and check 
  102. the device's identification bytes.  Note that the slot-number portion of the 
  103. unit number does not always represent the physical slot of the device, rather, 
  104. it sometimes represents the logical slot where you can find the address of the 
  105. device's driver entry point in the ProDOS global page.  For example, if a 
  106. SmartPort device interface in slot 5 has more than two connected devices, the 
  107. third and fourth devices will be mapped to slot 2; this mapping gives these 
  108. two devices unit numbers of $20 and $A0 respectively, but the device's driver 
  109. entry point will still be in the $C5xx address space.
  110.  
  111. ProDOS 8 Technical Note #20, Mirrored Devices and SmartPort, discusses this 
  112. kind of mapping in detail.  It also presents a code example which gives you 
  113. the correct device-driver entry point (from the global page) given the unit 
  114. number as input.  We repeat this code example below for your benefit.  It 
  115. assumes the unit_number is in the accumulator.
  116.  
  117.  
  118. devcnt    equ    $BF31
  119. devlst    equ    $BF32
  120. devadr    equ    $BF10
  121. devget    sta    unitno        ; store for later compare instruction
  122.           ldx    devcnt        ; get count-1 from $BF31
  123. devloop   lda    devlst,x      ; get entry in list
  124.           and    #$F0          ; mask off low nibble
  125. devcomp   cmp    unitno        ; compare to the unit_number we filled in
  126.           beq    goodnum       ;
  127.           dex
  128.           bpl    devloop       ; loop again if still less than $80
  129.           bmi    badunitno     ; error: bad unit number
  130. goodnum   lda    unitno        ; get good copy of unit_number
  131.           lsr    a             ; divide it by 8
  132.           lsr    a             ; (not sixteen because devadr entries are
  133.           lsr    a             ; two bytes wide)
  134.           tax
  135.           lda    devadr,x      ; low byte of device driver address
  136.           sta    addr
  137.           lda    devadr+1,x    ; high byte of device driver address
  138.           sta    addr+1
  139.           rts
  140. addr      dw     0             ; address will be filled in here by goodnum
  141. unitno    dfb    0             ; unit number storage
  142.  
  143. Warning:  Attempting to construct the device-driver entry point from 
  144.           the unit number is very dangerous.  Always use the 
  145.           technique presented above.
  146.  
  147.  
  148. Network Volumes
  149.  
  150. AppleTalk volumes present a special problem to some developers since they 
  151. appear as "phantom devices," or devices which do not always have a device 
  152. driver installed in the ProDOS global page.  Fortunately, the ProDOS Filing 
  153. Interface (PFI) to AppleTalk provides a way to identify network volumes 
  154. through an MLI call.  The ProDOS Filing Interface call FIListSessions is used 
  155. to retrieve a list of the current sessions being maintained through PFI and 
  156. any volumes mounted for those sessions.  The following presents an example:
  157.  
  158. Network   JSR    $BF00         ;ProDOS MLI
  159.           DFB    $42           ;AppleTalk command number
  160.           DW     ParamAddr     ;Address of Parameter Table
  161.           BCS    ERROR         ;error occurred
  162.  
  163. ParamAddr DFB    $00           ;Async Flag (0 means synchronous only)
  164.                                ;note there is no parameter count
  165.           DFB    $2F           ;command for FIListSessions
  166.           DW     $0000         ;AppleTalk Result Code returned here
  167.           DW     BufLength     ;length of the buffer supplied
  168.           DW     BufPointer    ;low word of pointer to buffer
  169.           DW     $0000         ;high word of pointer to buffer
  170.                                ;(THIS WILL NOT BE ZERO IF THE BUFFER IS
  171.                                ;NOT IN BANK ZERO!!!)
  172.           DFB    $00           ;Number of entries returned here
  173.  
  174. If the FIListSessions call fails with a bad command error ($01), then 
  175. AppleShare is not installed; therefore, there are no networks volumes mounted.  
  176. If there is a network error, the accumulator will contain $88 (Network Error), 
  177. and the result code in the parameter block will contain the specific error 
  178. code.  The list of current sessions is placed into the buffer (at the address 
  179. BufPointer in the example above), but if the buffer is not large enough to 
  180. hold the list, it will retain the maximum number of current sessions possible 
  181. and return an error with a result code of $0A0B (Buffer Too Small).  The 
  182. buffer format is as follows:
  183.  
  184. SesnRef   DFB    $00           ;Sessions Reference number (result)
  185. UnitNum   DFB    $00           ;Unit Number (result)
  186. VolName   DS     28            ;28 byte space for Volume Name
  187.                                ;(starts with a length byte)
  188. VolumeID  DW     $0000         ;Volume ID (result)
  189.  
  190. This list is repeated for every volume mounted for each session (the number is 
  191. placed into the last byte of the parameter list you passed to the ProDOS MLI).  
  192. For example, if there are two volumes mounted for session one, then session 
  193. one will be listed two times.  The UnitNum field contains the slot and drive 
  194. number in unit-number format, and note that bit zero of this byte is set if 
  195. the volume is a user volume (i.e., it contains a special "users" folder).  
  196. This distinction is unimportant for identifying a ProDOS device as a network 
  197. pseudo-device, but it is necessary for applications which need to know the 
  198. location of the user volume.  Note that if you mount two servers or more with 
  199. each having its own user volume, the user volume found first in the list 
  200. (scanned top to bottom) returned by FIListSessions specifies the user volume 
  201. that an application should use.  See the AppleShare Programmer's Guide for the 
  202. Apple IIGS (available from the Apple Programmer's and Developer's Association 
  203. (APDA)) for more information on programming for network volumes.
  204.  
  205. If you keep a list of all unit numbers returned by the ON_LINE call and mark 
  206. each one "identified" as you identify it, keep in mind that the unit numbers 
  207. returned by FIListSessions and ON_LINE have different low nibbles which should 
  208. be masked off before you make any comparisons.
  209.  
  210. Note:  You should mark the network volumes as identified and not 
  211.        try to identify them further with the following methods.
  212.  
  213.  
  214. What Slot is it Really In?
  215.  
  216. Once you have the address of the device driver's entry point and know that the 
  217. device is not a network pseudo-device, you can determine in what physical slot 
  218. the device resides.  If the high byte of the device driver's entry point is of 
  219. the form $Cn, then n is the physical slot number of the device.  A SmartPort 
  220. device mirrored to slot 2 will have a device driver address of $C5xx, giving 5 
  221. as the physical slot number.
  222.  
  223. If the high byte of the device driver entry point is not of the form $Cn, 
  224. then there are three other possibilities:
  225.  
  226.   o  The device is a Disk II with driver code inside ProDOS.
  227.   o  The device is either /RAM with driver code inside ProDOS or a 
  228.      third-party auxiliary-slot RAM disk device with driver code 
  229.      installed somewhere in memory.
  230.   o  The device is not a RAM disk but has a RAM-based device driver, 
  231.      like a third-party network device.
  232.  
  233. Auxiliary-slot RAM disks are identified by convention.  Any device in slot 3, 
  234. drive 2 (unit number $B0) is assumed to be an auxiliary-slot RAM disk since 
  235. ProDOS 8 will not recognize any card which is not an 80-column card in slot 3 
  236. (see ProDOS 8 Technical Note #15).  There is a chance that some other kind of 
  237. device could be installed with unit number $B0, but it is not likely.
  238.  
  239. To identify various kinds of auxiliary-slot RAM disks, you must obtain the 
  240. unit number from the ProDOS global page.  The list of unit numbers starts at 
  241. $BF32 (DEVLST) and is preceded by the number of unit numbers minus one 
  242. (DEVCNT, at $BF31).  You should search through this list until you find a unit 
  243. number in the form $Bx; if the unit number is $B3, $B7, $BB, or $BF, you can 
  244. assume the device to be an auxiliary-slot RAM disk which uses the auxiliary 
  245. 64K bank of memory present in a 128K Apple IIe or IIc, or a IIGS.  If the unit 
  246. number is one of the four listed above, you must remove this device to safely 
  247. access memory in the auxiliary 64K bank, but if the unit number is not one of 
  248. the four listed above, you can assume the device to be an auxiliary-slot RAM 
  249. disk which does not use the normal bank of auxiliary memory.  (Some third-
  250. party auxiliary-slot cards contain more than one 64K auxiliary bank; the 
  251. normal use of this memory is as a RAM disk.  If the RAM-based driver for this 
  252. kind of card does not use the normal auxiliary 64K bank for storage, it should 
  253. have a unit number other than one of the four listed above.)  If the unit 
  254. number is not one of the four listed above, you may safely access the 
  255. auxiliary bank of memory without first removing this device.
  256.  
  257. Section 5.2.2.3 of the ProDOS 8 Technical Reference Manual contains a routine 
  258. which disconnects the appropriate RAM disk devices in slot 3, drive 2, without 
  259. removing those drivers which do not use that bank, to allow use of the 
  260. auxiliary 64K bank.
  261.  
  262. Note:  Previous information from Apple indicated that /RAM could be 
  263.        distinguished from third-party RAM disks by a driver address of 
  264.        $FF00.  Although the address has not changed, some third-party 
  265.        drivers may have addresses of $FF00 as well, although this is not 
  266.        supported.  /RAM always has a driver address of $FF00 and unit 
  267.        number $BF, although any third-party RAM disk could install itself 
  268.        with similar attributes.
  269.  
  270. For Disk II devices, the three-bit slot number portion of the unit_number will 
  271. always be the physical slot number.  Disk II devices can never be mirrored to 
  272. another slot (the Disk II driver does not support it); therefore, it will be 
  273. in the physical slot represented in the unit number which ProDOS assigns when 
  274. it boots.
  275.  
  276. If the high byte of the device driver's entry point is not of the form $Cn, 
  277. then you should assume that the slot number is the value SSS in the unit 
  278. number (this is equivalent to assuming the device is a Disk II) for the next 
  279. step, which is checking the I/O space for identification bytes.
  280.  
  281.  
  282. What to Do With the Slot Number
  283.  
  284. Once you have the slot number, you can look at the slot I/O ROM space to 
  285. determine the kind of device it is.  As described in the ProDOS 8 Technical 
  286. Reference Manual, ProDOS looks for the following ID bytes in ROM to determine 
  287. if a ProDOS device is in a slot:
  288.  
  289.     $Cn01 = $20
  290.     $Cn03 = $00
  291.     $Cn05 = $03
  292.  
  293. If you use the slot number, n, you obtained above, and the three values listed 
  294. above are not present, then the device has a RAM-based driver and cannot 
  295. further be identified.
  296.  
  297. If the three values previously discussed are present, then examination of 
  298. $CnFF will give more information.  If $CnFF = $00, the device is a Disk II.  
  299. If $CnFF is any value other than $00 or $FF ($FF signifies a 13-sector Disk 
  300. II, which ProDOS does not support), the device is a ProDOS block device.
  301.  
  302. For ProDOS block devices, the byte at $CnFE contains several flags which 
  303. further identify the device; these flags are discussed in section 6.3.1 of the 
  304. ProDOS 8 Technical Reference Manual.
  305.  
  306.  
  307. SmartPort Devices
  308.  
  309. Many of Apple's ProDOS block devices follow the SmartPort firmware interface.  
  310. Through SmartPort, you can further identify devices.  Existing SmartPort 
  311. devices include SCSI hard disks, 3.5" disk drives and CD-ROM drives, with many 
  312. more possible device types.
  313.  
  314. If $Cn07 = $00, then the device is a SmartPort device, and you can then make a 
  315. SmartPort call to get more information about the device, including a device 
  316. type and subtype.  The SmartPort entry point is three bytes beyond the ProDOS 
  317. block device entry point, which you already determined above.  The method for 
  318. making SmartPort calls is outlined in the Apple IIc Technical Reference Manual 
  319. and the Apple IIGS Firmware Reference.
  320.  
  321. The most useful SmartPort call to make for device identification is the STATUS 
  322. call with statcode = 3 for Return Device Information Block (DIB).  This call 
  323. returns the ASCII name of the device, a device type and subtype, as well as 
  324. the size of the device.  Some SmartPort device types and subtypes are listed 
  325. in the referenced manuals, with a more complete list located in the Apple IIGS 
  326. Firmware Reference.  A list containing SmartPort device types only is provided 
  327. in SmartPort Technical Note #4, SmartPort Device Types.
  328.  
  329.  
  330. RAM-Based Drivers
  331.  
  332. One fork of the identification tree comes to an end at this point.  If the 
  333. high byte of the device driver entry point was not $Cn and the device was not 
  334. /RAM, we assumed it was a Disk II and used the slot number portion of the unit 
  335. number to examine the slot ROM space.  If the ROM space for that slot number 
  336. does not match the three ProDOS block device ID bytes, it cannot be a Disk II.  
  337. Having ruled out other possibilities, it must be a device installed after 
  338. ProDOS finished building its device table.  Perhaps it is a third-party RAM 
  339. disk driver or maybe a driver for an older card which does not match the 
  340. ProDOS block device ID bytes.
  341.  
  342. Whatever the function of the driver, you can identify it no further.  It quite 
  343. literally could be any kind of device at all, and with neither slot ROM space 
  344. to identify nor a standard location to compare the device driver entry point 
  345. against, the best you can do is consider it a "generic device" and go on.
  346.  
  347.  
  348. But Is It Connected, and Can I Read From It?
  349.  
  350. Just because a ProDOS device is in the table does not mean it is ready to be 
  351. used.  There is always the possibility that the drive has no media in it.  
  352. Back in the beginning, we made an ON_LINE call with a unit number of $00.  If 
  353. the volume name of a disk in that device could not be read, or another error 
  354. occurred, ProDOS 8 would return the error code to us in the ON_LINE buffer 
  355. immediately following the unit number.  Those errors possible include:
  356.  
  357.     $27    I/O error
  358.     $28    No Device Connected
  359.     $2B    Write Protected
  360.     $2F    Device off-line
  361.     $45    Volume directory not found
  362.     $52    Not a ProDOS disk
  363.     $55    Volume Control Block full
  364.     $56    Bad buffer address
  365.     $57    Duplicate volume on-line
  366.  
  367. Note that error $2F is not listed in the ProDOS 8 Technical Reference Manual.
  368.  
  369. By convention, we interpret I/O error to mean the disk in the drive is either 
  370. damaged or blank (not formatted).  We interpret Device off-line to mean that 
  371. there is no disk in the drive.  We interpret No Device Connected to mean the 
  372. drive really does not exist (for example, asking for status on a second Disk 
  373. II when only one is connected).
  374.  
  375. If no error occurred for a unit number in the ON_LINE call (the low nibble of 
  376. the unit number is not zero), the volume name of the disk in the drive follows 
  377. the unit number.
  378.  
  379.  
  380. Things To Avoid
  381.  
  382. The ProDOS device-level STATUS call generally returns the number of blocks on 
  383. a device.  Applications should not try to identify 3.5" drives by doing a 
  384. ProDOS or SmartPort STATUS call and comparing the number of blocks to 800 or 
  385. 1,600.  The correct way to identify a 3.5" drive is by the Type field in a 
  386. SmartPort STATUS call.
  387.  
  388. Don't assume the characteristics of a device just because it is in a certain 
  389. slot.  For example, be prepared to deal with 5.25" disk drives in slots other 
  390. than 6.  Don't assume that slot 6 is associated with block devices at all--
  391. there could be a printer card installed.
  392.  
  393. Avoid reinstalling /RAM when your application finds it removed.  If you remove 
  394. /RAM, you should reinstall it when you're done with the extra memory; however, 
  395. if your application finds /RAM already gone, you do not have the right to 
  396. just reinstall it.  A driver of some kind may be installed in auxiliary 
  397. memory, and arbitrary reinstallation of /RAM could bring the system down.
  398.  
  399.  
  400. Further Reference
  401. _____________________________________________________________________________
  402.     o    ProDOS 8 Technical Reference Manual
  403.     o    AppleShare Programmer's Guide for the Apple IIGS
  404.     o    ProDOS 8 Technical Note #15, How ProDOS 8 Treats Slot 3
  405.     o    ProDOS 8 Technical Note #20, Mirrored Devices and SmartPort